﻿using System;
using System.Collections;
using System.Globalization;

namespace ww.wwf.wwfbll
{
    /// <summary>
    /// 公式计算
    /// This class is used to convert a string expression to a numeric one, 
    /// to evaluate this numeric expression and to reconvert the result back
    /// to string
    /// </summary>
    public class FormulaGenerator
    {
        #region constructors
        /// <summary>
        /// implicit constructor
        /// </summary>
        public FormulaGenerator()
        {

        }//FormulaGenerator
        #endregion constructors


        #region public members
        public static string EvaluationResult(string astrexpr)
        {
            try
            {
                if (astrexpr == "") astrexpr = "0";
                EvalExpr(astrexpr.Replace(" ",""));
                return m_strservice;
            }
            catch //(Exception aobjExc)
            {
                //throw aobjExc;
                return "";
            }
        }//EvaluationResult
        #endregion public members


        #region private members
        //this alghoritm work  for expression with any level of parenthesis 
        private static void EvalExpr(string astrexpr)
        {
            if (ExistParenthesis(astrexpr))
            {
                int iposleftparenthesis = PosMaxLevel(astrexpr);
                string strtemp = astrexpr.Substring(iposleftparenthesis + 1);
                int iposrightparenthesis = FindFirstChar(strtemp, ')');
                string strbetweenparenthesis = strtemp.Substring(0, iposrightparenthesis);

                EvalAritm(strbetweenparenthesis.Trim());

                string strbefore = astrexpr.Substring(0, iposleftparenthesis);
                string strafter = astrexpr.Substring(iposleftparenthesis + iposrightparenthesis + 2);
                EvalExpr(strbefore + m_strservice + strafter);
            }
            else EvalAritm(astrexpr.Trim());

        }//EvalExpr


        private static bool ExistParenthesis(string astrexpr)
        {
            m_iCharContor = 0;
            int inbleft = 0;
            NbOfChar(astrexpr, '(');
            inbleft = m_iCharContor;

            m_iCharContor = 0;
            int inbright = 0;
            NbOfChar(astrexpr, ')');
            inbright = m_iCharContor;

            if (inbleft != inbright) throw new Exception("Sintax Error!");
            if (inbleft == 0) return false;
            return true;
        }//ExistParenthesis


        private static int PosMaxLevel(string astrexpr)
        {
            int ipos = -1;
            int ilevel = 0;
            int maxlevel = LevelOfParenthesis(astrexpr);

            foreach (char ch in astrexpr.ToCharArray())
            {
                ipos += 1;
                if (ch == '(')
                {
                    ilevel += 1;
                    if (ilevel == maxlevel)
                    {
                        return ipos;
                    }
                }
                else if (ch == ')')
                {
                    ilevel -= 1;
                }
            }

            return 0;
        }//PosMaxLevel



        private static int LevelOfParenthesis(string astrexpr)
        {
            int ilevel = 0;
            int ipos = -1;
            int maxlevel = 0;
            foreach (char ch in astrexpr.ToCharArray())
            {
                ipos += 1;
                if (ch == '(')
                {
                    ilevel = ilevel + 1;
                }
                else if (ch == ')')
                {
                    ilevel -= 1;
                }
                if (maxlevel < ilevel)
                {
                    maxlevel = ilevel;
                }
            }
            return maxlevel;
        }//LevelOfParenthesis



        private static int FindLastChar(string astrexpr, char acfinder)
        {
            return astrexpr.LastIndexOf(acfinder);
        }//FindLastChar


        private static int FindFirstChar(string astrexpr, char acfinder)
        {
            return astrexpr.IndexOf(acfinder);
        }//FindFirstChar


        private static int FindSecondChar(string astrexpr, char acfinder)
        {
            int ifirst = astrexpr.IndexOf(acfinder);
            int isecond = astrexpr.Substring(ifirst + 1).IndexOf(acfinder);
            return ifirst + isecond + 1;
        }//FindSecondChar


        private static void NbOfChar(string astrexpr, char acfinder)
        {
            int i = astrexpr.IndexOf(acfinder);
            if (i >= 0)
            {
                m_iCharContor += 1;
                NbOfChar(astrexpr.Substring(i + 1), acfinder);
            }
        }//NbOfChar


        private static void EvalAritm(string astrexpr)
        {
            ProcessPercent(astrexpr);
            string strwithoutpercent = m_strservice;

            ProcessDivision(strwithoutpercent);
            string strwithoutdivision = m_strservice;

            ProcessMultiply(strwithoutdivision);
            string strwithoutmultiply = m_strservice;

            ProcessMinus(strwithoutmultiply);
            string strwithoutminus = m_strservice;

            ProcessPlus(strwithoutminus);
            string strwithoutplus = m_strservice;
        }//EvalAritm


        private static void ProcessPercent(string astrexpr)
        {
            m_iCharContor = 0;
            NbOfChar(astrexpr, '%');
            int inbpercent = m_iCharContor;

            string strnewastrexpr = astrexpr.Trim();
            m_iCharContor = 0;
            NbOfChar(strnewastrexpr, '%');
            if (m_iCharContor == 0)
            {
                m_strservice = strnewastrexpr;
            }
            if (inbpercent > 0)
            {
                string astrexprwithoutbreak = astrexpr.Trim();
                int ipospercent = FindFirstChar(astrexprwithoutbreak, '%');
                string astrwithoutpercent;
                if (ipospercent >= 1)
                {
                    astrwithoutpercent = astrexprwithoutbreak.Substring(0, ipospercent);
                }
                else
                {
                    throw new Exception("Sintax error!");
                }

                int ilastdivision = FindLastChar(astrwithoutpercent, '/');
                int ilastmultiply = FindLastChar(astrwithoutpercent, '*');
                int ilastminus = FindLastChar(astrwithoutpercent, '-');
                int ilastplus = FindLastChar(astrwithoutpercent, '+');


                ArrayList arlsigns = new ArrayList();
                arlsigns.Add(ilastdivision);
                arlsigns.Add(ilastmultiply);
                arlsigns.Add(ilastminus);
                arlsigns.Add(ilastplus);
                int imaxsignpos = NbMax(arlsigns);
                if (imaxsignpos < 0) imaxsignpos = 0;

                string strpercent;
                string strbeforepercent;
                if (imaxsignpos >= 1)
                {
                    strpercent = astrwithoutpercent.Substring(imaxsignpos + 1).Trim();
                    strbeforepercent = astrwithoutpercent.Substring(0, imaxsignpos + 1).Trim();
                }
                else
                {
                    strpercent = astrwithoutpercent.Trim();
                    strbeforepercent = "";
                }

                string strafterpercent = "";
                if (ipospercent < astrexprwithoutbreak.Length - 1)
                {
                    strafterpercent = astrexprwithoutbreak.Substring(ipospercent + 1).Trim();
                }

                decimal dpercentvalue = ConvertToValue(strpercent);
                strnewastrexpr = strbeforepercent + Convert.ToString(dpercentvalue) + strafterpercent;
                ProcessPercent(strnewastrexpr);
            }
        }//ProcessPercent


        private static void ProcessDivision(string astrexpr)
        {
            m_iCharContor = 0;
            NbOfChar(astrexpr, '/');
            int inbdivision = m_iCharContor;

            string strnewastrexpr = astrexpr.Trim();
            m_iCharContor = 0;
            NbOfChar(strnewastrexpr, '/');
            if (m_iCharContor == 0)
            {
                m_strservice = strnewastrexpr;
            }

            if (inbdivision > 0)
            {
                string astrexprwithoutbreak = astrexpr.Trim();
                int iposdivision = FindFirstChar(astrexprwithoutbreak, '/');
                string astrbeforedivision;
                if (iposdivision >= 1)
                {
                    astrbeforedivision = astrexprwithoutbreak.Substring(0, iposdivision).Trim();
                }
                else
                {
                    throw new Exception("Division error!");
                }

                string astrafterdivision;
                if (iposdivision < astrexprwithoutbreak.Length - 1)
                {
                    astrafterdivision = astrexprwithoutbreak.Substring(iposdivision + 1).Trim();
                }
                else
                {
                    throw new Exception("Division error!");
                }

                int ilastdivisionbefore = FindLastChar(astrbeforedivision, '/');
                int ilastmultiplybefore = FindLastChar(astrbeforedivision, '*');
                int ilastminusbefore = FindLastChar(astrbeforedivision, '-');
                int ilastplusbefore = FindLastChar(astrbeforedivision, '+');

                int ilastdivisionafter = FindFirstChar(astrafterdivision, '/');
                int ilastmultiplyafter = FindFirstChar(astrafterdivision, '*');
                int ilastminusafter = FindFirstChar(astrafterdivision, '-');
                int ilastplusafter = FindFirstChar(astrafterdivision, '+');

                ArrayList arlsignsbefore = new ArrayList();
                arlsignsbefore.Add(ilastdivisionbefore);
                arlsignsbefore.Add(ilastmultiplybefore);
                arlsignsbefore.Add(ilastminusbefore);
                arlsignsbefore.Add(ilastplusbefore);
                int imaxsignpos = NbMax(arlsignsbefore);
                if (imaxsignpos <= 0) imaxsignpos = -1;

                ArrayList arlsignsafter = new ArrayList();
                arlsignsafter.Add(ilastdivisionafter);
                arlsignsafter.Add(ilastmultiplyafter);
                arlsignsafter.Add(ilastminusafter);
                arlsignsafter.Add(ilastplusafter);
                int iminsignpos = NbMin(arlsignsafter);
                if (iminsignpos <= 0) iminsignpos = 0;

                string strbeforedivisionafter = astrbeforedivision.Substring(imaxsignpos + 1).Trim();
                string strbeforedivisionbefore = astrbeforedivision.Substring(0, imaxsignpos + 1).Trim();

                string strafterdivisionbefore = astrafterdivision.Substring(0, iminsignpos).Trim();
                string strafterdivisionafter = astrafterdivision.Substring(iminsignpos).Trim();

                bool issignbefore = false;
                if (strbeforedivisionbefore.Length > 0)
                {
                    if (strbeforedivisionbefore.Substring(0, 1).Trim() == "-")
                    {
                        issignbefore = true;
                    }
                }

                bool issignafter = false;
                if (strafterdivisionbefore.Length > 0)
                {
                    if (strafterdivisionbefore.Substring(0, 1).Trim() == "-")
                    {
                        issignafter = true;
                    }
                }

                decimal dbeforedivision;
                if (strbeforedivisionafter.Length > 0)
                {
                    dbeforedivision = Convert.ToDecimal(SetDecimalSeparator(strbeforedivisionafter));
                }
                else if (strbeforedivisionbefore.Length > 0)
                {
                    dbeforedivision = Convert.ToDecimal(SetDecimalSeparator(strbeforedivisionbefore));
                }
                else dbeforedivision = 0;

                decimal dafterdivision;
                if (strafterdivisionbefore.Length > 0)
                {
                    dafterdivision = Convert.ToDecimal(SetDecimalSeparator(strafterdivisionbefore));
                }
                else if (strafterdivisionafter.Length > 0)
                {
                    dafterdivision = Convert.ToDecimal(SetDecimalSeparator(strafterdivisionafter));
                }
                else dafterdivision = 1;

                decimal ddivision = 0;
                if (dafterdivision != 0)
                {
                    if (issignbefore || issignafter)
                    {
                        ddivision = (-1) * dbeforedivision / dafterdivision;
                    }
                    else ddivision = dbeforedivision / dafterdivision;
                }

                strnewastrexpr = strbeforedivisionbefore + Convert.ToString(ddivision) + strafterdivisionafter;
                if (strafterdivisionbefore == "") strnewastrexpr = strbeforedivisionbefore + Convert.ToString(ddivision);
                ProcessDivision(strnewastrexpr);
            }
        }//ProcessDivision



        private static void ProcessMultiply(string astrexpr)
        {
            m_iCharContor = 0;
            NbOfChar(astrexpr, '*');
            int inbmultiply = m_iCharContor;

            string strnewastrexpr = astrexpr.Trim();
            m_iCharContor = 0;
            NbOfChar(strnewastrexpr, '*');
            if (m_iCharContor == 0)
            {
                m_strservice = strnewastrexpr;
            }

            if (inbmultiply > 0)
            {
                string astrexprwithoutbreak = astrexpr.Trim();
                int iposmultiply = FindFirstChar(astrexprwithoutbreak, '*');
                string astrbeforemultiply;
                if (iposmultiply >= 1)
                {
                    astrbeforemultiply = astrexprwithoutbreak.Substring(0, iposmultiply).Trim();
                }
                else
                {
                    throw new Exception("Error!");
                }

                string astraftermultiply;
                if (iposmultiply < astrexprwithoutbreak.Length - 1)
                {
                    astraftermultiply = astrexprwithoutbreak.Substring(iposmultiply + 1).Trim();
                }
                else
                {
                    throw new Exception("Error!");
                }

                int ilastdivisionbefore = FindLastChar(astrbeforemultiply, '/');
                int ilastmultiplybefore = FindLastChar(astrbeforemultiply, '*');
                int ilastminusbefore = FindLastChar(astrbeforemultiply, '-');
                int ilastplusbefore = FindLastChar(astrbeforemultiply, '+');

                int ilastdivisionafter = FindFirstChar(astraftermultiply, '/');
                int ilastmultiplyafter = FindFirstChar(astraftermultiply, '*');
                int ilastminusafter = FindFirstChar(astraftermultiply, '-');
                int ilastplusafter = FindFirstChar(astraftermultiply, '+');

                ArrayList arlsignsbefore = new ArrayList();
                arlsignsbefore.Add(ilastdivisionbefore);
                arlsignsbefore.Add(ilastmultiplybefore);
                arlsignsbefore.Add(ilastminusbefore);
                arlsignsbefore.Add(ilastplusbefore);
                int imaxsignpos = NbMax(arlsignsbefore);
                if (imaxsignpos <= 0) imaxsignpos = -1;

                ArrayList arlsignsafter = new ArrayList();
                arlsignsafter.Add(ilastdivisionafter);
                arlsignsafter.Add(ilastmultiplyafter);
                arlsignsafter.Add(ilastminusafter);
                arlsignsafter.Add(ilastplusafter);
                int iminsignpos = NbMin(arlsignsafter);
                if (iminsignpos <= 0) iminsignpos = 0;

                string strbeforemultiplyafter = astrbeforemultiply.Substring(imaxsignpos + 1).Trim();
                string strbeforemultiplybefore = astrbeforemultiply.Substring(0, imaxsignpos + 1).Trim();

                string straftermultiplybefore = astraftermultiply.Substring(0, iminsignpos).Trim();
                string straftermultiplyafter = astraftermultiply.Substring(iminsignpos).Trim();

                bool issignbefore = false;
                if (strbeforemultiplybefore.Length > 0)
                {
                    if (strbeforemultiplybefore.Substring(0, 1).Trim() == "-")
                    {
                        //issignbefore = true;
                    }
                }

                bool issignafter = false;
                if (straftermultiplybefore.Length > 0)
                {
                    if (straftermultiplybefore.Substring(0, 1).Trim() == "-")
                    {
                        issignafter = true;
                    }
                }

                decimal dbeforemultiply;
                if (strbeforemultiplyafter.Length > 0)
                {
                    if (IsDigit(strbeforemultiplyafter) == true)
                    {
                        dbeforemultiply = Convert.ToDecimal(SetDecimalSeparator(strbeforemultiplyafter));
                    }
                    else
                    {
                        dbeforemultiply = ConvertToValue(strbeforemultiplyafter);
                    }
                }
                else if (strbeforemultiplybefore.Length > 0)
                {
                    if (IsDigit(strbeforemultiplybefore) == true)
                    {
                        dbeforemultiply = Convert.ToDecimal(SetDecimalSeparator(strbeforemultiplybefore));
                    }
                    else
                    {
                        dbeforemultiply = ConvertToValue(strbeforemultiplybefore);
                    }
                }
                else dbeforemultiply = 0;

                decimal daftermultiply;
                if (straftermultiplybefore.Length > 0)
                {
                    if (IsDigit(straftermultiplybefore) == true)
                    {
                        daftermultiply = Convert.ToDecimal(SetDecimalSeparator(straftermultiplybefore));
                    }
                    else
                    {
                        daftermultiply = ConvertToValue(straftermultiplybefore);
                    }
                }
                else if (straftermultiplyafter.Length > 0)
                {
                    if (IsDigit(straftermultiplyafter) == true)
                    {
                        daftermultiply = Convert.ToDecimal(SetDecimalSeparator(straftermultiplyafter));
                    }
                    else
                    {
                        daftermultiply = ConvertToValue(straftermultiplyafter);
                    }
                }
                else daftermultiply = 0;

                decimal dmultiply = 0;
                if (daftermultiply != 0)
                {
                    if (issignbefore || issignafter)
                    {
                        dmultiply = (-1) * dbeforemultiply * daftermultiply;
                    }
                    else dmultiply = dbeforemultiply * daftermultiply;
                }

                strnewastrexpr = strbeforemultiplybefore + Convert.ToString(dmultiply) + straftermultiplyafter;
                if (straftermultiplybefore == "") strnewastrexpr = strbeforemultiplybefore + Convert.ToString(dmultiply);
                ProcessMultiply(strnewastrexpr);
            }
        }//ProcessMultiply


        private static void ProcessMinus(string astrexpr)
        {
            m_iCharContor = 0;
            NbOfChar(astrexpr, '-');

            int iposminustest = FindFirstChar(astrexpr.Trim(), '-');
            //if(iposminustest == 0) iposminustest = this.FindSecondChar(astrexpr.Trim(),'-');

            string strnewastrexpr = astrexpr.Trim();
            m_iCharContor = 0;
            NbOfChar(strnewastrexpr, '-');
            if (iposminustest == 0) m_iCharContor -= 1;
            int inbminus = m_iCharContor;
            if (m_iCharContor == 0)
            {
                m_strservice = strnewastrexpr;
            }

            if (inbminus > 0)
            {
                string astrexprwithoutbreak = astrexpr.Trim();
                //if(iposminustest == 0) astrexprwithoutbreak = astrexprwithoutbreak.Substring(1);
                int iposminus = FindFirstChar(astrexprwithoutbreak, '-');
                if (iposminus == 0) iposminus = FindSecondChar(astrexprwithoutbreak, '-');
                string astrbeforeminus;
                if (iposminus >= 1)
                {
                    astrbeforeminus = astrexprwithoutbreak.Substring(0, iposminus).Trim();
                }
                else
                {
                    astrbeforeminus = astrexprwithoutbreak.Substring(0, iposminus).Trim();
                }

                string astrafterminus;
                if (iposminus < astrexprwithoutbreak.Length - 1)
                {
                    astrafterminus = astrexprwithoutbreak.Substring(iposminus + 1).Trim();
                    //if(iposminustest == 0)astrafterminus = astrafterminus.Substring(1).Trim();
                }
                else
                {
                    throw new Exception("Error!");
                }

                int ilastdivisionbefore = FindLastChar(astrbeforeminus, '/');
                int ilastmultiplybefore = FindLastChar(astrbeforeminus, '*');
                int ilastminusbefore = FindLastChar(astrbeforeminus, '-');
                int ilastplusbefore = FindLastChar(astrbeforeminus, '+');

                int ilastdivisionafter = FindFirstChar(astrafterminus, '/');
                int ilastmultiplyafter = FindFirstChar(astrafterminus, '*');
                int ilastminusafter = FindFirstChar(astrafterminus, '-');
                int ilastplusafter = FindFirstChar(astrafterminus, '+');

                ArrayList arlsignsbefore = new ArrayList();
                arlsignsbefore.Add(ilastdivisionbefore);
                arlsignsbefore.Add(ilastmultiplybefore);
                arlsignsbefore.Add(ilastminusbefore);
                arlsignsbefore.Add(ilastplusbefore);
                int imaxsignpos = NbMax(arlsignsbefore);
                if (imaxsignpos <= 0) imaxsignpos = -1;

                ArrayList arlsignsafter = new ArrayList();
                arlsignsafter.Add(ilastdivisionafter);
                arlsignsafter.Add(ilastmultiplyafter);
                arlsignsafter.Add(ilastminusafter);
                arlsignsafter.Add(ilastplusafter);
                int iminsignpos = NbMin(arlsignsafter);
                if (iminsignpos <= 0) iminsignpos = 0;

                string strbeforeminusafter = astrbeforeminus.Substring(imaxsignpos + 1).Trim();
                string strbeforeminusbefore = astrbeforeminus.Substring(0, imaxsignpos + 1).Trim();

                string strafterminusbefore = astrafterminus.Substring(0, iminsignpos).Trim();
                string strafterminusafter = astrafterminus.Substring(iminsignpos).Trim();

                decimal dbeforeminus = 0;
                if (strbeforeminusafter.Length > 0)
                {
                    if (IsDigit(strbeforeminusafter) == true)
                    {
                        dbeforeminus = Convert.ToDecimal(SetDecimalSeparator(strbeforeminusafter));
                    }
                    else
                    {
                        dbeforeminus = ConvertToValue(strbeforeminusafter);
                    }
                }
                else if (strbeforeminusbefore.Length > 0)
                {
                    if (IsDigit(strbeforeminusbefore) == true)
                    {
                        dbeforeminus = Convert.ToDecimal(SetDecimalSeparator(strbeforeminusbefore));
                    }
                    else
                    {
                        dbeforeminus = ConvertToValue(strbeforeminusbefore);
                    }
                }

                decimal dafterminus = 0;
                if (strafterminusbefore.Length > 0)
                {
                    if (IsDigit(strafterminusbefore))
                    {
                        dafterminus = Convert.ToDecimal(SetDecimalSeparator(strafterminusbefore));
                    }
                    else
                    {
                        dafterminus = ConvertToValue(strafterminusbefore);
                    }
                }
                else if (strafterminusafter.Length > 0)
                {
                    if (IsDigit(strafterminusafter))
                    {
                        dafterminus = Convert.ToDecimal(SetDecimalSeparator(strafterminusafter));
                    }
                    else
                    {
                        dafterminus = ConvertToValue(strafterminusafter);
                    }
                }

                decimal dminus = 0;
                dminus = dbeforeminus - dafterminus;

                strnewastrexpr = strbeforeminusbefore + Convert.ToString(dminus) + strafterminusafter;
                if (strafterminusbefore == "") strnewastrexpr = strbeforeminusbefore + Convert.ToString(dminus);

                ProcessMinus(strnewastrexpr);
            }
        }//ProcessMinus


        private static void ProcessPlus(string astrexpr)
        {
            m_iCharContor = 0;
            NbOfChar(astrexpr, '+');
            int inbplus = m_iCharContor;

            string strnewastrexpr = astrexpr.Trim();
            m_iCharContor = 0;
            NbOfChar(strnewastrexpr, '+');
            if (m_iCharContor == 0)
            {
                m_strservice = strnewastrexpr;
            }

            if (inbplus > 0)
            {
                string astrexprwithoutbreak = astrexpr.Trim();
                int iposplus = FindFirstChar(astrexprwithoutbreak, '+');
                string astrbeforeplus;
                if (iposplus >= 1)
                {
                    astrbeforeplus = astrexprwithoutbreak.Substring(0, iposplus).Trim();
                }
                else
                {
                    throw new Exception("Error!");
                }

                string astrafterplus;
                if (iposplus < astrexprwithoutbreak.Length - 1)
                {
                    astrafterplus = astrexprwithoutbreak.Substring(iposplus + 1).Trim();
                }
                else
                {
                    throw new Exception("Error!");
                }

                int ilastdivisionbefore = FindLastChar(astrbeforeplus, '/');
                int ilastmultiplybefore = FindLastChar(astrbeforeplus, '*');
                int ilastminusbefore = FindLastChar(astrbeforeplus, '-');
                int ilastplusbefore = FindLastChar(astrbeforeplus, '+');

                int ilastdivisionafter = FindFirstChar(astrafterplus, '/');
                int ilastmultiplyafter = FindFirstChar(astrafterplus, '*');
                int ilastminusafter = FindFirstChar(astrafterplus, '-');
                int ilastplusafter = FindFirstChar(astrafterplus, '+');

                ArrayList arlsignsbefore = new ArrayList();
                arlsignsbefore.Add(ilastdivisionbefore);
                arlsignsbefore.Add(ilastmultiplybefore);
                arlsignsbefore.Add(ilastminusbefore);
                arlsignsbefore.Add(ilastplusbefore);
                int imaxsignpos = NbMax(arlsignsbefore);
                if (imaxsignpos <= 0) imaxsignpos = -1;

                ArrayList arlsignsafter = new ArrayList();
                arlsignsafter.Add(ilastdivisionafter);
                arlsignsafter.Add(ilastmultiplyafter);
                arlsignsafter.Add(ilastminusafter);
                arlsignsafter.Add(ilastplusafter);
                int iminsignpos = NbMin(arlsignsafter);
                if (iminsignpos <= 0) iminsignpos = 0;

                string strbeforeplusafter = astrbeforeplus.Substring(imaxsignpos + 1).Trim();
                string strbeforeplusbefore = astrbeforeplus.Substring(0, imaxsignpos + 1).Trim();

                string strafterplusbefore = astrafterplus.Substring(0, iminsignpos).Trim();
                string strafterplusafter = astrafterplus.Substring(iminsignpos).Trim();

                decimal dbeforeplus = 0;
                if (strbeforeplusafter.Length > 0)
                {
                    if (IsDigit(strbeforeplusafter) == true)
                    {
                        dbeforeplus = Convert.ToDecimal(SetDecimalSeparator(strbeforeplusafter));
                    }
                    else
                    {
                        dbeforeplus = ConvertToValue(strbeforeplusafter);
                    }
                }
                else if (strbeforeplusbefore.Length > 0)
                {
                    if (IsDigit(strbeforeplusbefore) == true)
                    {
                        dbeforeplus = Convert.ToDecimal(SetDecimalSeparator(strbeforeplusbefore));
                    }
                    else
                    {
                        dbeforeplus = ConvertToValue(strbeforeplusbefore);
                    }
                }


                decimal dafterplus = 0;
                if (strafterplusbefore.Length > 0)
                {
                    if (IsDigit(strafterplusbefore) == true)
                    {
                        dafterplus = Convert.ToDecimal(SetDecimalSeparator(strafterplusbefore));
                    }
                    else
                    {
                        dafterplus = ConvertToValue(strafterplusbefore);
                    }
                }
                else if (strafterplusafter.Length > 0)
                {
                    if (IsDigit(strafterplusafter) == true)
                    {
                        dafterplus = Convert.ToDecimal(SetDecimalSeparator(strafterplusafter));
                    }
                    else
                    {
                        dafterplus = ConvertToValue(strafterplusafter);
                    }
                }


                decimal dplus = 0;
                dplus = dbeforeplus + dafterplus;

                strnewastrexpr = strbeforeplusbefore + Convert.ToString(dplus) + strafterplusafter;
                if (strafterplusbefore == "") strnewastrexpr = strbeforeplusbefore + Convert.ToString(dplus);
                ProcessPlus(strnewastrexpr);
            }
            else
            {
                if (IsDigit(astrexpr) == false)
                {
                    ConvertToValue(astrexpr);
                }
            }
        }//ProcessPlus


        private static decimal ConvertToValue(string astrexpr)
        {

            bool bmarker = true;
            decimal dexpr = 0;
            for (int i = 0; i <= astrexpr.Length - 1; i++)
            {
                string strlocal = astrexpr.Substring(i, 1);
                if ((i != 0) || (strlocal != "-"))
                {
                    char[] ch = strlocal.ToCharArray();
                    if ((Char.IsDigit(ch[0]) == false) && (strlocal != ".") && (strlocal != ",") /*&& (strlocal != " ")*/)
                    {
                        bmarker = false;
                    }
                }
            }

            if (bmarker == true)
            {
                dexpr = Convert.ToDecimal(astrexpr) / 100;
            }
            else
            {

                throw new Exception("Not numeric value!");
            }

            return dexpr;
        }//ConvertToValue


        private static int NbMax(ArrayList aobjarl)
        {
            int max = 0;
            foreach (object obj in aobjarl)
            {
                if ((int)obj != -1)
                {
                    if (max <= (int)obj) max = (int)obj;
                }
            }
            return max;
        }//NbMax


        private static int NbMin(ArrayList aobjarl)
        {
            int min = NbMax(aobjarl);
            foreach (object obj in aobjarl)
            {
                if ((int)obj != -1)
                {
                    if (min >= (int)obj) min = (int)obj;
                }
            }
            return min;
        }//NbMin


        private static bool IsDigit(string astrexpr)
        {
            foreach (char ch in astrexpr.ToCharArray())
            {
                if ((ch != '-') && (ch != ' ') && (ch != '.') && (ch != ','))
                {
                    if (Char.IsDigit(ch) == false)
                    {
                        return false;
                    }
                }
            }
            return true;
        }//IsDigit


        private static string SetDecimalSeparator(string astrexpr)
        {
            string strseparator = NumberFormatInfo.CurrentInfo.NumberDecimalSeparator;
            int ipoint = astrexpr.IndexOf('.');
            int icomma = astrexpr.IndexOf(',');
            string newastrexpr;

            if (ipoint >= 0)
            {
                newastrexpr = astrexpr.Replace(".", strseparator);
            }
            else if (icomma >= 0)
            {
                newastrexpr = astrexpr.Replace(",", strseparator);
            }
            else
            {
                newastrexpr = astrexpr;
            }
            return newastrexpr;
        }//SetDecimalSeparator


        private static int m_iCharContor = 0;
        private static string m_strservice = "";
        //private static double m_iNbOfMinus = 0;
        //private static string m_strExpression;



        #endregion private members

    }
}
